package icu.sunway.gushenBlogBackEnd.Service.Implement;

import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import icu.sunway.gushenBlogBackEnd.Entity.Data.ArticleDO;
import icu.sunway.gushenBlogBackEnd.Entity.Data.LikeDO;
import icu.sunway.gushenBlogBackEnd.Entity.Data.UserDO;
import icu.sunway.gushenBlogBackEnd.Entity.View.ResultVO;
import icu.sunway.gushenBlogBackEnd.Mapper.LikeMapper;
import icu.sunway.gushenBlogBackEnd.Message.LikeMessage;
import icu.sunway.gushenBlogBackEnd.Service.LikeService;
import icu.sunway.gushenBlogBackEnd.utils.DateUtils;
import icu.sunway.gushenBlogBackEnd.utils.JwtUtil;
import org.springframework.stereotype.Service;

import java.util.List;

@Service
public class LikeServiceImpl extends ServiceImpl<LikeMapper, LikeDO> implements LikeService {

    private final UserServiceImpl userServiceImpl;
    private final ArticleServiceImpl articleServiceImpl;

    LikeServiceImpl(UserServiceImpl userServiceImpl, ArticleServiceImpl articleServiceImpl) {
        this.userServiceImpl = userServiceImpl;
        this.articleServiceImpl = articleServiceImpl;
    }

    @Override
    public ResultVO<Boolean> addLike(String article_id, String token) {
        try {
            String user_id = JwtUtil.parseTokenAsId(token);
            QueryWrapper<LikeDO> queryWrapper = new QueryWrapper<>();
            queryWrapper.eq("article_id", article_id);
            queryWrapper.eq("user_id", user_id);
            if (getOne(queryWrapper) != null) {
                throw new Exception("用户已经收藏过该文章");
            }
            UserDO userDO = userServiceImpl.getById(user_id);
            ArticleDO articleDO = articleServiceImpl.getById(article_id);
            save(new LikeDO(null,
                    user_id,
                    article_id,
                    userDO.getNickname(),
                    articleDO.getTitle(), DateUtils.getCurDateString())
            );
        } catch (Exception e) {
            return new ResultVO<>(400, LikeMessage.add_like_fail + " " + e.getMessage(), false);
        }
        return new ResultVO<>(200, LikeMessage.add_like_success, true);
    }

    @Override
    public ResultVO<Boolean> removeLike(String id) {
        try {
            removeById(id);
        } catch (Exception e) {
            return new ResultVO<>(400, LikeMessage.remove_like_fail, false);
        }
        return new ResultVO<>(200, LikeMessage.remove_like_success, true);
    }

    @Override
    public ResultVO<List<LikeDO>> getLikeList() {
        List<LikeDO> likeDOList;
        try {
            QueryWrapper<LikeDO> queryWrapper = new QueryWrapper<>();
            queryWrapper.orderByDesc("like_time");
            likeDOList = list(queryWrapper);
        } catch (Exception e) {
            return new ResultVO<>(400, LikeMessage.get_like_fail, null);
        }
        return new ResultVO<>(200, LikeMessage.get_like_success, likeDOList);
    }

    @Override
    public ResultVO<Long> getLikeCountFromArticle(String article_id) {
        long likeCount;
        try {
            QueryWrapper<LikeDO> queryWrapper = new QueryWrapper<>();
            queryWrapper.eq("article_id", article_id);
            likeCount = count(queryWrapper);
        } catch (Exception e) {
            return new ResultVO<>(400, LikeMessage.get_like_count_fail, null);
        }
        return new ResultVO<>(200, LikeMessage.get_like_count_success, likeCount);
    }

    @Override
    public ResultVO<Boolean> checkIsLiked(String article_id, String token) {
        try {
            QueryWrapper<LikeDO> queryWrapper = new QueryWrapper<>();
            queryWrapper.eq("article_id", article_id);
            queryWrapper.eq("user_id", JwtUtil.parseTokenAsId(token));
            if (getOne(queryWrapper) == null) {
                throw new Exception();
            }
        } catch (Exception e) {
            return new ResultVO<>(400, LikeMessage.check_like_fail, false);
        }
        return new ResultVO<>(200, LikeMessage.check_like_success, true);
    }

    @Override
    public ResultVO<Boolean> removeLikeFromArticle(String article_id, String token) {
        try {
            QueryWrapper<LikeDO> queryWrapper = new QueryWrapper<>();
            queryWrapper.eq("article_id", article_id);
            queryWrapper.eq("user_id", JwtUtil.parseTokenAsId(token));
            if (!remove(queryWrapper)) {
                throw new Exception();
            }
        } catch (Exception e) {
            return new ResultVO<>(400, LikeMessage.remove_like_fail, false);
        }
        return new ResultVO<>(200, LikeMessage.remove_like_success, true);
    }

    @Override
    public ResultVO<List<LikeDO>> getLikeListByUser(String token) {
        List<LikeDO> likeDOList;
        try {
            QueryWrapper<LikeDO> queryWrapper = new QueryWrapper<>();
            queryWrapper.eq("user_id", JwtUtil.parseTokenAsId(token));
            queryWrapper.orderByDesc("like_time");
            likeDOList = list(queryWrapper);
            if (likeDOList == null) {
                throw new Exception();
            }
        } catch (Exception e) {
            return new ResultVO<>(400, LikeMessage.get_like_fail, null);
        }
        return new ResultVO<>(200, LikeMessage.get_like_success, likeDOList);
    }

    @Override
    public ResultVO<Long> getLikeCountFromUser(String token) {
        long likeCount;
        try {
            QueryWrapper<LikeDO> queryWrapper = new QueryWrapper<>();
            queryWrapper.eq("user_id", JwtUtil.parseTokenAsId(token));
            likeCount = count(queryWrapper);
        } catch (Exception e) {
            return new ResultVO<>(400, LikeMessage.get_like_count_fail, null);
        }
        return new ResultVO<>(200, LikeMessage.get_like_count_success, likeCount);
    }

    @Override
    public ResultVO<List<LikeDO>> getLikeListByUserByPage(String token, int curPage, int pageSize) {
        List<LikeDO> likeDOList;
        try {
            Page<LikeDO> likeDOPage = new Page<>(curPage, pageSize);
            QueryWrapper<LikeDO> queryWrapper = new QueryWrapper<>();
            queryWrapper.eq("user_id", JwtUtil.parseTokenAsId(token));
            queryWrapper.orderByDesc("like_time");
            IPage<LikeDO> likeDOIPage = page(likeDOPage, queryWrapper);
            likeDOList = likeDOIPage.getRecords();
        } catch (Exception e) {
            return new ResultVO<>(400, LikeMessage.get_like_fail, null);
        }
        return new ResultVO<>(200, LikeMessage.get_like_success, likeDOList);
    }

}
